import 'package:flutter/material.dart';

/// 分页加载视图类型
enum PaginationSliverViewType {
  /// 列表视图
  listView,
  /// 网格视图
  gridView,
}

/// 网格布局配置
class PaginationSliverGridConfig {
  /// 每行列数
  final int crossAxisCount;
  /// 子项宽高比
  final double childAspectRatio;
  /// 主轴间距
  final double mainAxisSpacing;
  /// 交叉轴间距
  final double crossAxisSpacing;
  /// 子项主轴扩展（如果设置，childAspectRatio 将被忽略）
  final double? mainAxisExtent;

  const PaginationSliverGridConfig({
    this.crossAxisCount = 2,
    this.childAspectRatio = 1.0,
    this.mainAxisSpacing = 8.0,
    this.crossAxisSpacing = 8.0,
    this.mainAxisExtent,
  });
}

/// 分页控制器接口
abstract class PaginationSliverController<T> {
  /// 加载数据的主要方法
  /// [currentPage] 当前页码（从1开始）
  /// [pageSize] 每页数据量
  /// [hasMore] 是否还有更多数据
  /// 返回当前页的数据列表
  Future<List<T>> loadDatas(int currentPage, int pageSize, bool hasMore);

  /// 判断是否还有更多数据
  /// [currentPageDataLength] 当前页数据长度
  /// [totalRecordsLength] 总记录数
  /// [pageSize] 每页数据量
  bool hasMore(int currentPageDataLength, int totalRecordsLength, int pageSize);

  /// 处理加载状态变化
  /// [isLoading] 是否正在加载
  void curState(bool isLoading);

  /// 获取所有已加载的数据
  /// [records] 所有已加载的数据列表
  void onResultAllList(List<T> records);
}

/// 支持 Header 的分页加载组件
class PaginationSliverView<T> extends StatefulWidget {
  /// 分页控制器
  final PaginationSliverController<T> controller;
  
  /// 列表项构建器
  final Widget Function(BuildContext context, T item, int index) itemBuilder;
  
  /// 视图类型
  final PaginationSliverViewType viewType;
  
  /// 网格布局配置（仅在 gridView 模式下有效）
  final PaginationSliverGridConfig? gridConfig;
  
  /// 每页数据量
  final int pageSize;
  
  /// 滚动触发距离
  final double triggerDistance;
  
  /// 头部组件
  final Widget? header;
  
  /// 顶部 Sliver 组件列表
  final List<Widget>? topSlivers;
  
  /// 底部 Sliver 组件列表
  final List<Widget>? bottomSlivers;
  
  /// 内边距
  final EdgeInsets padding;
  
  /// 是否支持下拉刷新
  final bool enableRefresh;
  
  /// 刷新回调
  final Future<void> Function()? onRefresh;
  
  /// 加载指示器
  final Widget? loadingIndicator;
  
  /// 空数据指示器
  final Widget? emptyIndicator;
  
  /// 错误指示器
  final Widget Function(String? errorMessage, VoidCallback onRetry)? errorIndicator;
  
  /// 没有更多数据指示器
  final Widget? noMoreDataIndicator;
  
  /// 自定义内容构建器
  /// 如果提供，将使用此方法构建内容区域，而不是默认的 ListView/GridView
  /// 如果返回 null，将使用默认的内容构建逻辑
  /// 参数：
  /// - [context] 构建上下文
  /// - [items] 当前已加载的数据列表
  /// - [isLoading] 是否正在加载
  /// - [hasMore] 是否还有更多数据
  /// - [errorMessage] 错误信息（如果有）
  final Widget? Function(
    BuildContext context,
    List<T> items,
    bool isLoading,
    bool hasMore,
    String? errorMessage,
  )? contentBuilder;
  
  /// 外部滚动控制器
  final ScrollController? scrollController;

  const PaginationSliverView({
    super.key,
    required this.controller,
    required this.itemBuilder,
    this.viewType = PaginationSliverViewType.listView,
    this.gridConfig,
    this.pageSize = 20,
    this.triggerDistance = 200.0,
    this.header,
    this.topSlivers,
    this.bottomSlivers,
    this.padding = const EdgeInsets.all(16),
    this.enableRefresh = true,
    this.onRefresh,
    this.loadingIndicator,
    this.emptyIndicator,
    this.errorIndicator,
    this.noMoreDataIndicator,
    this.contentBuilder,
    this.scrollController,
  });

  @override
  State<PaginationSliverView<T>> createState() => _PaginationSliverViewState<T>();
}

class _PaginationSliverViewState<T> extends State<PaginationSliverView<T>> {
  // 数据管理
  List<T> _allItems = [];
  bool _isLoading = false;
  bool _hasMore = true;
  int _currentPage = 1;
  String? _errorMessage;
  
  // 滚动控制
  late ScrollController _scrollController;

  @override
  void initState() {
    super.initState();
    // 使用外部滚动控制器或创建新的
    _scrollController = widget.scrollController ?? ScrollController();
    _scrollController.addListener(_onScroll);
    _loadInitialData();
  }

  @override
  void dispose() {
    _scrollController.removeListener(_onScroll);
    // 只有在使用内部滚动控制器时才释放
    if (widget.scrollController == null) {
      _scrollController.dispose();
    }
    super.dispose();
  }

  void _onScroll() {
    if (_scrollController.position.pixels >= 
        _scrollController.position.maxScrollExtent - widget.triggerDistance) {
      _loadMoreData();
    }
  }

  Future<void> _loadInitialData() async {
    if (_isLoading) return;
    
    setState(() {
      _isLoading = true;
      _currentPage = 1;
      _errorMessage = null;
    });
    
    try {
      final items = await widget.controller.loadDatas(1, widget.pageSize, _hasMore);
      setState(() {
        _allItems = items;
        _isLoading = false;
        _hasMore = widget.controller.hasMore(items.length, items.length, widget.pageSize);
      });
      
      widget.controller.curState(false);
      widget.controller.onResultAllList(_allItems);
    } catch (e) {
      setState(() {
        _isLoading = false;
        _errorMessage = e.toString();
      });
      widget.controller.curState(false);
    }
  }

  Future<void> _loadMoreData() async {
    if (_isLoading || !_hasMore) return;
    
    setState(() {
      _isLoading = true;
    });
    
    try {
      final items = await widget.controller.loadDatas(_currentPage + 1, widget.pageSize, _hasMore);
      setState(() {
        _allItems.addAll(items);
        _currentPage++;
        _isLoading = false;
        _hasMore = widget.controller.hasMore(items.length, _allItems.length, widget.pageSize);
      });
      
      widget.controller.curState(false);
      widget.controller.onResultAllList(_allItems);
    } catch (e) {
      setState(() {
        _isLoading = false;
        _errorMessage = e.toString();
      });
      widget.controller.curState(false);
    }
  }

  Future<void> _onRefresh() async {
    if (widget.onRefresh != null) {
      await widget.onRefresh!();
    }
    await _loadInitialData();
  }

  Widget _buildLoadingIndicator() {
    if (widget.loadingIndicator != null) {
      return widget.loadingIndicator!;
    }
    
    return const Center(
      child: Padding(
        padding: EdgeInsets.all(16.0),
        child: CircularProgressIndicator(),
      ),
    );
  }

  Widget _buildEmptyIndicator() {
    if (widget.emptyIndicator != null) {
      return widget.emptyIndicator!;
    }
    
    return const Center(
      child: Padding(
        padding: EdgeInsets.all(32.0),
        child: Text(
          '暂无数据',
          style: TextStyle(
            fontSize: 16,
            color: Colors.grey,
          ),
        ),
      ),
    );
  }

  Widget _buildErrorIndicator() {
    if (widget.errorIndicator != null) {
      return widget.errorIndicator!(_errorMessage, _loadInitialData);
    }
    
    return Center(
      child: Padding(
        padding: const EdgeInsets.all(32.0),
        child: Column(
          mainAxisSize: MainAxisSize.min,
          children: [
            const Icon(
              Icons.error_outline,
              size: 64,
              color: Colors.red,
            ),
            const SizedBox(height: 16),
            Text(
              _errorMessage ?? '加载失败',
              style: const TextStyle(
                fontSize: 16,
                color: Colors.red,
              ),
            ),
            const SizedBox(height: 16),
            ElevatedButton(
              onPressed: _loadInitialData,
              child: const Text('重试'),
            ),
          ],
        ),
      ),
    );
  }

  Widget _buildNoMoreDataIndicator() {
    if (widget.noMoreDataIndicator != null) {
      return widget.noMoreDataIndicator!;
    }
    
    return const Padding(
      padding: EdgeInsets.all(16.0),
      child: Center(
        child: Text(
          '已加载全部数据',
          style: TextStyle(
            fontSize: 14,
            color: Colors.grey,
          ),
        ),
      ),
    );
  }

  Widget _buildContentSliver() {
    // 如果提供了自定义内容构建器，使用它
    if (widget.contentBuilder != null) {
      final content = widget.contentBuilder!(
        context,
        _allItems,
        _isLoading,
        _hasMore,
        _errorMessage,
      );
      // 如果返回 null，使用默认逻辑
      if (content == null) {
        return _buildDefaultContent();
      }
      return SliverToBoxAdapter(child: content);
    }
    
    // 使用默认的内容构建逻辑
    return _buildDefaultContent();
  }

  /// 默认内容构建逻辑
  Widget _buildDefaultContent() {
    if (_errorMessage != null) {
      return SliverToBoxAdapter(
        child: _buildErrorIndicator(),
      );
    }
    
    // 第一次加载时显示 loading
    if (_allItems.isEmpty && _isLoading) {
      return SliverToBoxAdapter(
        child: _buildLoadingIndicator(),
      );
    }
    
    if (_allItems.isEmpty && !_isLoading) {
      return SliverToBoxAdapter(
        child: _buildEmptyIndicator(),
      );
    }

    if (widget.viewType == PaginationSliverViewType.gridView) {
      return _buildGridView();
    } else {
      return _buildListView();
    }
  }

  Widget _buildListView() {
    return SliverPadding(
      padding: widget.padding,
      sliver: SliverList(
        delegate: SliverChildBuilderDelegate(
          (context, index) {
            if (index < _allItems.length) {
              return widget.itemBuilder(context, _allItems[index], index);
            }
            return null;
          },
          childCount: _allItems.length,
        ),
      ),
    );
  }

  Widget _buildGridView() {
    final config = widget.gridConfig ?? const PaginationSliverGridConfig();
    
    return SliverPadding(
      padding: widget.padding,
      sliver: SliverGrid(
        gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
          crossAxisCount: config.crossAxisCount,
          childAspectRatio: config.childAspectRatio,
          mainAxisSpacing: config.mainAxisSpacing,
          crossAxisSpacing: config.crossAxisSpacing,
          mainAxisExtent: config.mainAxisExtent,
        ),
        delegate: SliverChildBuilderDelegate(
          (context, index) {
            if (index < _allItems.length) {
              return widget.itemBuilder(context, _allItems[index], index);
            }
            return null;
          },
          childCount: _allItems.length,
        ),
      ),
    );
  }

  Widget _buildStatusSliver() {
    // 只在加载更多时显示 loading（不是第一次加载）
    if (_isLoading && _allItems.isNotEmpty) {
      return SliverToBoxAdapter(
        child: _buildLoadingIndicator(),
      );
    }
    
    // 显示结束提示
    if (!_hasMore && _allItems.isNotEmpty) {
      return SliverToBoxAdapter(
        child: _buildNoMoreDataIndicator(),
      );
    }
    
    return const SliverToBoxAdapter(child: SizedBox.shrink());
  }

  @override
  Widget build(BuildContext context) {
    return CustomScrollView(
      controller: _scrollController,
      physics: widget.enableRefresh 
          ? const AlwaysScrollableScrollPhysics()
          : const ClampingScrollPhysics(),
      slivers: [
        // 顶部 Sliver 组件
        if (widget.topSlivers != null) ...widget.topSlivers!,
        
        // 头部组件
        if (widget.header != null)
          SliverToBoxAdapter(child: widget.header!),
        
        // 内容区域
        _buildContentSliver(),
        
        // 状态指示器（加载更多、结束提示等）
        _buildStatusSliver(),
        
        // 底部 Sliver 组件
        if (widget.bottomSlivers != null) ...widget.bottomSlivers!,
      ],
    );
  }
}
